Job System

¶àÏ̱߳à³Ì¼ÆË㣬Ö÷ҪΪÁËÌáÉýÐÔÄÜ¡£

 

ÐÔÄÜ·ÖÎö


 Playmode Æô¶¯·ÖÎö ¹´Ñ¡LiveʵʱÏÔʾÏß³ÌÐÅÏ¢

 


Ö»±£Áô½Å±¾

 

UnityÏîÄ¿ÒÀÀµµÄDOTS°ü°²×°£¨»ùÓÚunity2020 ¸ß°æ±¾¿ÉÄÜÖ±½ÓËÑË÷¾ÍÄÜ°²×°£©

Æô¶¯Edit > Project Settings > Package ManagerÖеÄEnable Preview Packages


 

Òª°²×°µÄ°üûÓР¿ÉÒÔͨ¹ýurl ÏÂÔØ

×îºÃ·­Ç½

°²×°com.unity.entities

°²×°com.unity.burst

°²×°com.unity.mathematics

°²×°com.unity.collections

»òÕßÖ±½Ó°²×°com.unity.rendering.hybrid(ÒÀÀµÉÏÃæ4¸ö°ü)

ÔÙ°²×°Ò»ÏÂcom.unity.jobs

 

Job SystemÓ﷨עÒâ


½á¹¹ÌåÖ»°üº¬blittableÀàÐÍÄÇô½á¹¹Ìå´´½¨µÄ±äÁ¿ Ò²ÊÇblittableÀàÐÍ

IJob»ù´¡Ê¹ÓÃ

using UnityEngine;

using Unity.Jobs;

using Unity.Mathematics;

using Unity.Collections;

using Unity.Burst;

 

[BurstCompile]

public struct Job1 : IJob

{

    public NativeArray<int> array1;

    public NativeArray<int> array2;

    public int index;

    public void Execute()

    {

        array2[index] = array1[index] + 1;

        Debug.Log(message: $"µ±Ç°Ï̠߳{System.Threading.Thread.CurrentThread.ManagedThreadId}");//´òÓ¡µ±Ç°Ïß³ÌID

    }

}

 

public class MyIJob : MonoBehaviour

{

    public int[] testArray = new int[] { 1, 2, 3 };

 

    void Start()

    {

        Debug.Log(message: $"Ö÷Ï̠߳{System.Threading.Thread.CurrentThread.ManagedThreadId}");//´òÓ¡µ±Ç°Ïß³ÌID

 

        NativeArray<int> array1 = new NativeArray<int>(testArray, Allocator.TempJob);//·ÇÍйÜÇøÉêÇëÄÚ´æ

        NativeArray<int> array2 = new NativeArray<int>(testArray, Allocator.TempJob);//·ÇÍйÜÇøÉêÇëÄÚ´æ

        Job1 jb = new Job1() { array1 = array1, array2 = array2, index = 2 };//´´½¨Job

        var jobHandle = jb.Schedule();//ÉêÇëÒ»¸öÏ̠߳¼ÆËã

        jobHandle.Complete();//¼ÆËãÍê³É

        array2.CopyTo(testArray);//¼ÆËã½á¹¹copyµ½²âÊÔÊý×é

        array1.Dispose();//ÊÍ·ÅÄÚ´æ

        array2.Dispose();//ÊÍ·ÅÄÚ´æ

    }

}

 

Allocator.Temp  ±£´æÒ»Õó

Allocator.TempJob ±£´æ4Ö¡

Allocator.Persistent ÔËÐÐÆÚ¼äÒ»Ö±´æÔÚ

 

* NativeArray Ö÷¶¯ÉêÇëÄÚ´æ Ê¹ÓúóÐèÒªÊͷŠʹÓÃblittableÀàÐÍ ²»ÒªÓÃÒýÓÃÀàÐÍ

 

Ö»¶ÁµÄ¿ÉÒÔÔÚ¶à¸öjobÖÐͬʱ¶ÁÈ¡£¬¿ÉÒÔ¿ªÆô¶à¸öjob


 

 

Èç¹ûÁ¬Ðø¿ªÆôÁ½¸öjob£¬ÏëÒªÔÚjob1»ù´¡ÉϽøÐÐjob2£¨ÏÈÖ´ÐÐjob1ºóÖ´ÐÐjob2£©¿ÉÒÔ

 

IJobParallelForTransform

Ö÷ÒªÊǸüÐÂÎïÌåµÄTransform

ÒÔÏÂΪÉú³É10000¸ö GameObject ²¢ÇÒ³¯×ÅÒ»¸öÎïÌåÒƶ¯£¬¸ßÐÔÄÜÒƶ¯ÎïÌå

 

using Unity.Collections;

using UnityEngine;

using UnityEngine.Jobs;

//**********************************

//×Ô¶¨ÒåÄ£°å´´½¨ÈË:Far

//**********************************

public struct EnemyMove : IJobParallelForTransform

{

    public NativeArray<Vector3> Velocity;

 

    public void Execute(int index, TransformAccess transform)

    {

        transform.position += Velocity[index] * 0.02f;

    }

}

 

using Unity.Collections;

using Unity.Entities;

using Unity.Jobs;

using UnityEngine;

using UnityEngine.Jobs;

//**********************************

//×Ô¶¨ÒåÄ£°å´´½¨ÈË:Far

//**********************************

//¹ÒÔص½Ò»¸ö¿ÕÎïÌåÉÏ

public class SetPos : MonoBehaviour

{

    public GameObject enemy;

    private TransformAccessArray tranAccessArray;

    private const int instanceCount = 10000;

 

    void Start()

    {

        tranAccessArray = new TransformAccessArray(instanceCount);

 

        for (int i = 0; i < instanceCount; i++)

        {

            var go = Instantiate(enemy);

            go.gameObject.SetActive(true);

            go.transform.position = Random.insideUnitSphere * 100;

            tranAccessArray.Add(go.transform);

        }

    }

 

    void Update()

    {

        var tempVelocity = new NativeArray<Vector3>(instanceCount, Allocator.TempJob);

        for (int i = 0; i < tempVelocity.Length; i++)

        {

            //tempVelocity[i] = Random.insideUnitSphere;

            tempVelocity[i] = transform.position - tranAccessArray[i].transform.position;

        }

 

        var job = new EnemyMove()

        { Velocity = tempVelocity };

 

        job.Schedule(tranAccessArray)// ÕâÀï´«ÈëTransformAccessArray

            .Complete();

 

        tempVelocity.Dispose();

    }

 

    private void OnDestroy()

    {

        tranAccessArray.Dispose();// ÐèÒªDispose£¡

    }

}